#-----------------------------------------------------------------------
# Makefile template for building CAM on various platforms.
#
# This makefile assumes the existence the file:
#
# Filepath      The directories, listed one per line, that contain the source
#               code required to build CAM.  This list is used to set the
#               VPATH variable which is used by GNU make to search for
#               dependencies (after it looks in the directory from which
#               it was invoked).  This list of directories, prepended with ./,
#               is also used to construct the list of search directories 
#               used by the preprocessor (as specified by -I command-line options).
#
# The following macros are set by CAM's configure script.  They should only be hand edited
# by experts.
#
# UNAMES        Result of the "uname -s" command on the target platform.
# ROOTDIR       Root directory for the CAM source distribution.
# EXENAME       Name of the executable.
# MODEL_EXEDIR  Directory to build the executable in.
# INC_NETCDF    Directory containing the NetCDF include files.
# LIB_NETCDF    Directory containing the NetCDF library.
# MOD_NETCDF    Directory containing the NetCDF module files.
# INC_MPI       Directory containing the MPI include files.
# LIB_MPI       Directory containing the MPI library.
# MPI_LIB_NAME  Name of MPI library.
# LAPACK_LIBDIR Directory containing the LAPACK library.
# ESMF_LIBDIR   Directory containing the ESMF library (for use with external library only).
# DEBUG         Set to TRUE to turn on compiler debugging options.  Default: FALSE 
# SPMD          Whether to build in SPMD mode or not. 	[values TRUE FALSE]
# SMP           Set to TRUE to enable building in SMP mode (uses OpenMP).  
# USER_FC       Allow user to override the default Fortran compiler specified in Makefile.
# FC_TYPE       Type of Fortran compiler invoked by generic wrapper script such as mpif90.
# USER_CC       Allow user to override the default C compiler specified in Makefile (linux only).
# USER_LINKER   Allow user to override the default linker specified in Makefile.
# USER_CPPDEFS  Additional CPP defines.
# USER_CFLAGS   Additional C compiler flags that the user wishes to set.
# USER_FFLAGS   Additional Fortran compiler flags that the user wishes to set.
# USER_LDLAGS   Additional load flags that the user wishes to set.
# F_OPTIMIZATION_OVERRIDE
#               Use this to replace default Fortran compiler optimization.
# COSP_LIBDIR   Directory where COSP library will be built.
#
# Note: An internal implementation of the ESMF time-manager interface is provided
#       with the sequential CCSM distribution in models/utils/esmf_wrf_timemgr.
#
#------------------------------------------------------------------------

# Set up special characters
null  :=
space := $(null) $(null)
comma := $(null),$(null)

# Initialize macros that allow a user override.
# *** N.B. *** Only the Linux architure observes the override for FC and CC.

# Set user specified Fortran compiler
ifneq ($(strip $(USER_FC)),)
  FC := $(USER_FC)
endif
# Set user override of default Fortran compiler optimizations
ifneq ($(strip $(F_OPTIMIZATION_OVERRIDE)),)
  FORTRAN_OPTIMIZATION := $(F_OPTIMIZATION_OVERRIDE)
endif
# Set user specified C compiler
ifneq ($(strip $(USER_CC)),)
  CC := $(USER_CC)
endif
# Set user specified linker
ifneq ($(strip $(USER_LINKER)),)
  LINKER := $(USER_LINKER)
endif

# Load dependency search path.
dirs := . $(shell cat Filepath)

# Set cpp search path, include netcdf
cpp_dirs := $(dirs) $(INC_NETCDF) $(INC_MPI) $(INC_PNETCDF)
cpp_path := $(foreach dir,$(cpp_dirs),-I$(dir)) # format for command line

# Expand any tildes in directory names. Change spaces to colons.
VPATH    := $(foreach dir,$(cpp_dirs),$(wildcard $(dir))) 
VPATH    := $(subst $(space),:,$(VPATH))               

#------------------------------------------------------------------------
# Primary target: build the model
#------------------------------------------------------------------------
#touch filepath to ensure Depends and Srcfiles are regenerated
all: $(MODEL_EXEDIR)/$(EXENAME) touch_filepath

touch_filepath:
	touch $(CURDIR)/Filepath

# Get list of files and build dependency file for all .o files
#   using perl scripts mkSrcfiles and mkDepends

SOURCES   := $(shell cat Srcfiles)

# Newer makes set the CURDIR variable.
CURDIR := $(shell pwd)

$(CURDIR)/Depends: $(CURDIR)/Srcfiles $(CURDIR)/Filepath
	$(ROOTDIR)/models/atm/cam/bld/mkDepends Filepath Srcfiles > $@

$(CURDIR)/Srcfiles: $(CURDIR)/Filepath
	$(ROOTDIR)/models/atm/cam/bld/mkSrcfiles > $@

OBJS      := $(addsuffix .o, $(basename $(SOURCES)))

CPPDEF    := -DNO_SHR_VMATH -DSEQ_MCT $(USER_CPPDEFS)
ifeq ($(SPMD),TRUE)
   CPPDEF += -DSPMD
endif

ifneq ($(strip $(LIB_PNETCDF)),)
  CPPDEF += -D_PNETCDF -DUSEMPIIO
  #dont use LDFLAGS here, it will be overwritten below
  USER_LDFLAGS += -L$(LIB_PNETCDF) -lpnetcdf 
endif

$(MODEL_EXEDIR)/$(EXENAME): $(OBJS)
	$(LINKER) -o $@ $(OBJS) -L$(LIB_NETCDF) -lnetcdf $(LDFLAGS) 

ifneq ($(strip $(COSP_LIBDIR)),)
# Rules to build COSP in its own library.  Add abortutils dependency so
# cosp code can make use of subroutine endrun.
$(COSP_LIBDIR)/libcosp.a: abortutils.o
	$(MAKE) -C $(COSP_LIBDIR)

cospsimulator_intr.o: $(COSP_LIBDIR)/libcosp.a
endif


# Compilation rules:
.SUFFIXES:
.SUFFIXES: .F .F90 .f90 .c .s .o

.F.o:
	$(FC) -c $(FIXEDFLAGS) $(FFLAGS) $<

.F90.o:
	$(FC) -c $(FREEFLAGS) $(FFLAGS) $<

.f90.o:
	$(FC) -c $(FREEFLAGS) $(FFLAGS) $<

.c.o:
	$(CC) -c $(CFLAGS) $<

.s.o:
	$(AS) -m  $<

# Rules used for the tests run by "configure -test"
test_fc: test_fc.o
	$(LINKER) -o $@ test_fc.o $(LDFLAGS)
test_nc: test_nc.o
	$(LINKER) -o $@ test_nc.o -L$(LIB_NETCDF) -lnetcdf $(LDFLAGS)
test_mpi: test_mpi.o
	$(LINKER) -o $@ test_mpi.o $(LDFLAGS)
test_esmf: test_esmf.o
	$(LINKER) -o $@ test_esmf.o $(LDFLAGS)


debug: $(OBJS)
	echo "FC: $(FC)"
	echo "FFLAGS: $(FFLAGS)"
	echo "LINKER: $(LINKER)"
	echo "LDFLAGS: $(LDFLAGS)"
	echo "OBJS: $(OBJS)"


clean:
	$(RM) $(MODEL_EXEDIR)/$(EXENAME) $(OBJS)

#------------------------------------------------------------------------
# AIX
#------------------------------------------------------------------------

ifeq ($(UNAMES),AIX)

CPPDEF     += -DAIX
ifeq ($(SMP),TRUE)
  # THREADED_OMP is used by the timing library
  CPPDEF   += -DTHREADED_OMP
endif

cpre = $(null)-WF,-D$(null)
FPPFLAGS   := $(patsubst -D%,$(cpre)%,$(CPPDEF))

# Use the thread-safe compilers even when disabling openMP.
ifeq ($(SPMD),TRUE)
  FC       := mpxlf90_r
else
  FC       := xlf90_r
endif

CC             := mpcc_r
CFLAGS         := -q64 $(cpp_path) $(CPPDEF)
mod_path       := -I$(MOD_NETCDF)
ifneq ($(strip $(COSP_LIBDIR)),)
  mod_path     += -I$(COSP_LIBDIR)
endif
FC_FLAGS       := -q64 -qarch=auto -qspillsize=2500 -g -qfullpath
FC_FLAGS_NOOPT := $(FC_FLAGS)
FREEFLAGS      := -qsuffix=f=f90:cpp=F90
FIXEDFLAGS     := -qfixed=132
LDFLAGS        := -q64 -lmassv -bdatapsize:64k -bstackpsize:64k -btextpsize:32k

ifeq ($(SMP),TRUE)
  FC_FLAGS_NOOPT += -qsmp=omp:noopt

  # -qsmp implicitly turns on -O2.  Explicitly disable this for debugging.
  ifeq ($(DEBUG),TRUE)
    FC_FLAGS += -qsmp=omp:noopt
    CFLAGS   += -qsmp=omp:noopt
    LDFLAGS  += -qsmp=omp:noopt
  else
    FC_FLAGS += -qsmp=omp
    CFLAGS   += -qsmp=omp
    LDFLAGS  += -qsmp=omp
  endif
endif

ifeq ($(SPMD),TRUE)
  LDFLAGS += -lmpi_r
else
  FPPFLAGS  += -WF,-DHIDE_MPI,-D_MPISERIAL,-DNO_MPI2
endif

ifeq ($(DEBUG),TRUE)
  # Bounds checking is unreliable on the IBM.
  # Sometimes you can get it to go if you turn threading off.
  # Only turn float-trapping on for debug mode as it's a 20% performance hit.
  FC_FLAGS       += -qinitauto=7FF7FFFF -qflttrap=ov:zero:inv:en

  # As of Apr/15/2003 cam2_0_2_dev18 xlfrte8.1.0.3 using -lmass causes the code to core-dump
  # when using DEBUG compiler options.
else
  # Check for override of default Fortran compiler optimizations
  ifeq ($(F_OPTIMIZATION_OVERRIDE),$(null))
    # Inline when not debugging
    FORTRAN_OPTIMIZATION := -O2 -qstrict -Q
  endif
  FC_FLAGS += $(FORTRAN_OPTIMIZATION)
  CFLAGS   += -O2
  LDFLAGS  += -lmass
endif

ifneq ($(strip $(LAPACK_LIBDIR)),)
  LDFLAGS += -L$(LAPACK_LIBDIR) -llapack -lblas
endif

FFLAGS       := $(cpp_path) $(mod_path) $(FPPFLAGS) $(FC_FLAGS)
FFLAGS_NOOPT := $(cpp_path) $(mod_path) $(FPPFLAGS) $(FC_FLAGS_NOOPT)
FC_AUTO_R8   := -qrealsize=8

# These RRTMG files take an extraordinarily long time to compile with optimization.
# Until mods are made to read the data from files, just remove optimization from
# their compilation.
rrtmg_lw_k_g.o: rrtmg_lw_k_g.f90
	$(FC) -c $(FREEFLAGS) $(FFLAGS_NOOPT) $<
rrtmg_sw_k_g.o: rrtmg_sw_k_g.f90
	$(FC) -c $(FREEFLAGS) $(FFLAGS_NOOPT) $<

endif

#------------------------------------------------------------------------
# SGI - IRIX
#------------------------------------------------------------------------

ifeq ($(UNAMES),IRIX64)

CPPDEF      += -DIRIX64
FC          := f90
CC          := cc
CFLAGS      := -64 $(cpp_path) $(CPPDEF) -O2
mod_path    := -I$(MOD_NETCDF)
FFLAGS      := -64 $(cpp_path) $(mod_path) $(CPPDEF) -i4 -macro_expand -extend_source
FREEFLAGS   :=
FIXEDFLAGS  :=
LDFLAGS     := -64

ifeq ($(DEBUG),TRUE)
  # WARNING: -mp and -g together has been known to cause wrong answers
  FFLAGS  += -g -DEBUG:trap_uninitialized=ON -C
else
  # Check for override of default Fortran compiler optimizations
  ifeq ($(F_OPTIMIZATION_OVERRIDE),$(null))
    FORTRAN_OPTIMIZATION := -O2
  endif
  FFLAGS += $(FORTRAN_OPTIMIZATION)
endif

ifeq ($(SMP),TRUE)
  # THREADED_OMP is used by the timing library
  CFLAGS += -DTHREADED_OMP
  # Only enable OpenMP, not SGI specific parallelism
  # Note that -lmp should precede -lmpi when running hybrid MPI/OpenMP
  FFLAGS  += -mp -MP:dsm=OFF -MP:old_mp=OFF
  CFLAGS  += -mp -MP:dsm=OFF -MP:old_mp=OFF
  LDFLAGS += -mp -lmp
endif

ifeq ($(SPMD),TRUE)
  FFLAGS  += -I$(INC_MPI)
  LDFLAGS += -L$(LIB_MPI) -lmpi
else
  FFLAGS  += -DHIDE_MPI -D_MPISERIAL -DNO_MPI2
endif

endif

#------------------------------------------------------------------------
# Linux
#------------------------------------------------------------------------

ifeq ($(UNAMES),Linux)

CPPDEF += -DLINUX

# Set the default Fortran compiler if not set by user
ifeq ($(strip $(USER_FC)),)
  FC := pgf90
endif

# Set the default Fortran compiler type if not set by user
ifeq ($(strip $(FC_TYPE)),)

  # By default assume the type is pgi, but then override this if a recognized
  # compiler name has been specified.
  FC_TYPE := pgi

  ifeq ($(FC),lf95)
    FC_TYPE := lahey
  endif

  ifeq ($(findstring ifort,$(FC)),ifort)
    FC_TYPE := intel
  endif

  ifeq ($(FC),pathf90)
    FC_TYPE := pathscale
  endif

  ifeq ($(FC),g95)
    FC_TYPE := g95
  endif

endif

# Set the default C compiler if not set by user
ifeq ($(strip $(USER_CC)),)
  ifeq ($(FC_TYPE),pgi)

    # recognize the special case on the Cray-XT platform: if ftn is the fortran
    # compiler wrapper and the underlying compiler is pgi then use cc rather than pgcc
    ifeq ($(FC),ftn)
      CC := cc
    else
      CC := pgcc
    endif

  else
    CC := cc
  endif
endif

ifeq ($(SMP),TRUE)
  # THREADED_OMP is used by the timing library
  CPPDEF += -DTHREADED_OMP
endif

CFLAGS = $(cpp_path) $(CPPDEF)

# Set search path for module files for external libraries.
mod_path := -I$(MOD_NETCDF)
ifneq ($(strip $(COSP_LIBDIR)),)
  mod_path += -I$(COSP_LIBDIR)
endif

# PGI

ifeq ($(FC_TYPE),pgi)

  CPPDEF        += -DNO_R16
  CFLAGS        += -O2 -Mvect=nosse 
  FC_FLAGS      := -i4 -Mdalign -Mextend -byteswapio
  FC_FLAGS_NOOPT:= $(FC_FLAGS)
  FREEFLAGS     := -Mfree
  FIXEDFLAGS    := -Mfixed
  LDFLAGS       :=

  ifeq ($(DEBUG),TRUE)
    FC_FLAGS       += -g -Ktrap=fp -Mbounds -Kieee
  else
    # Check for override of default Fortran compiler optimizations
    ifeq ($(F_OPTIMIZATION_OVERRIDE),$(null))
      FORTRAN_OPTIMIZATION := -gopt -O2 -Mvect=nosse -Kieee
    endif
    FC_FLAGS += $(FORTRAN_OPTIMIZATION)
  endif

  ifeq ($(SMP),TRUE)
    FC_FLAGS       += -mp
    FC_FLAGS_NOOPT += -mp
    CFLAGS         += -mp
    LDFLAGS        += -mp
  endif

  FFLAGS       := $(cpp_path) $(mod_path) $(CPPDEF) $(FC_FLAGS)
  FFLAGS_NOOPT := $(cpp_path) $(mod_path) $(CPPDEF) $(FC_FLAGS_NOOPT)
  FC_AUTO_R8   := -r8

# These RRTMG files cause a compiler error when using optimization.
# Until mods are made to read the data from files, just remove optimization from
# their compilation.
rrtmg_lw_k_g.o: rrtmg_lw_k_g.f90
	$(FC) -c $(FREEFLAGS) $(FFLAGS_NOOPT) $<
rrtmg_sw_k_g.o: rrtmg_sw_k_g.f90
	$(FC) -c $(FREEFLAGS) $(FFLAGS_NOOPT) $<

endif

# Lahey

ifeq ($(FC_TYPE),lahey)

  FC_FLAGS      := --wide
  FC_FLAGS_NOOPT:= $(FC_FLAGS)
  FREEFLAGS     :=
  FIXEDFLAGS    := --fix
  LDFLAGS       := --staticlink

  ifeq ($(DEBUG),TRUE)
    # --trace produces a call traceback on abort
    # --trap causes code to stop on divide by zero or overflow exceptions
    # --pca prevents overwriting constant arguments, but it overrides the
    #       action of --chk a.  So don't specify both.
    # --chk for basic compiler checking (a,e,s,u,x)
    #TBH:  this works    FFLAGS += -g --chk --pca
    #TBH:  this FAILS    FFLAGS += -g --chk a,e,s,u,x --pca
    FC_FLAGS       += -g --chk a,e,s,u --trace --trap
  else
    # Check for override of default Fortran compiler optimizations
    ifeq ($(F_OPTIMIZATION_OVERRIDE),$(null))
      FORTRAN_OPTIMIZATION := -O
    endif
    FC_FLAGS    += $(FORTRAN_OPTIMIZATION)
    # Threading only works by putting thread memory on the heap rather than the stack (--threadheap).
    # As of lf95 version 6.2 the thread stacksize limits are (still) too small to run even small
    # resolution problems (FV at 10x15 res fails).
    ifeq ($(SMP),TRUE)
      FC_FLAGS       += --openmp --threadheap 4096
      FC_FLAGS_NOOPT += --openmp --threadheap 4096
      CFLAGS         += -fstack-check
      LDFLAGS        += --openmp --threadheap 4096
    endif
  endif

  FFLAGS       := $(cpp_path) $(mod_path) $(CPPDEF) $(FC_FLAGS)
  FFLAGS_NOOPT := $(cpp_path) $(mod_path) $(CPPDEF) $(FC_FLAGS_NOOPT)
  FC_AUTO_R8   := -CcdRR8

binary_io.o: binary_io.F90
	$(FC) -c $(FREEFLAGS) $(FFLAGS_NOOPT) $<
wrap_nf.o: wrap_nf.F90
	$(FC) -c $(FREEFLAGS) $(FFLAGS_NOOPT) $<
wrap_mpi.o: wrap_mpi.F90
	$(FC) -c $(FREEFLAGS) $(FFLAGS_NOOPT) $<
apex_subs.o: apex_subs.F90
	$(FC) -c $(FREEFLAGS) $(FFLAGS_NOOPT) $<

endif

# Intel

ifeq ($(FC_TYPE),intel)

  FC_FLAGS      := -ftz -convert big_endian -fp-model precise 
  FC_FLAGS_NOOPT:= -ftz -convert big_endian -O0
  FREEFLAGS     := 
  FIXEDFLAGS    := -132
  LDFLAGS       := -static-intel

  ifeq ($(DEBUG),TRUE)
    FC_FLAGS       += -check all -fpe0 -g -traceback
  else
    # Check for override of default Fortran compiler optimizations
    ifeq ($(F_OPTIMIZATION_OVERRIDE),$(null))
      FORTRAN_OPTIMIZATION := -O2
    endif
    FC_FLAGS += $(FORTRAN_OPTIMIZATION)
  endif

  ifeq ($(SMP),TRUE)
    FC_FLAGS       += -openmp
    FC_FLAGS_NOOPT += -openmp
    CFLAGS         += -openmp
    LDFLAGS        += -openmp
  endif

  ifeq ($(USER_CC),$(null))
    CC := icc
  endif

  FFLAGS      := $(cpp_path) $(mod_path) $(CPPDEF) $(FC_FLAGS)
  FFLAGS_NOOPT:= $(cpp_path) $(mod_path) $(CPPDEF) $(FC_FLAGS_NOOPT)
  FC_AUTO_R8  := -autodouble

# These RRTMG files take an extraordinarily long time to compile with optimization.
# Until mods are made to read the data from files, just remove optimization from
# their compilation.
rrtmg_lw_k_g.o: rrtmg_lw_k_g.f90
	$(FC) -c $(FREEFLAGS) $(FFLAGS_NOOPT) $<
rrtmg_sw_k_g.o: rrtmg_sw_k_g.f90
	$(FC) -c $(FREEFLAGS) $(FFLAGS_NOOPT) $<
shr_scam_mod.o: shr_scam_mod.F90
	$(FC) -c $(FREEFLAGS) $(FFLAGS_NOOPT) $<

endif

# Pathscale

ifeq ($(FC_TYPE),pathscale)

  ifeq ($(USER_CC),$(null))
    CC            := pathcc
  endif
  CPPDEF        += -DNO_R16
  FC_FLAGS      := -extend_source -ftpp -fno-second-underscore
  FC_FLAGS_NOOPT:= $(FC_FLAGS) -O0
  FREEFLAGS     :=
  FIXEDFLAGS    :=
  LDFLAGS       :=

  ifeq ($(SMP),TRUE)
    FC_FLAGS       += -mp
    FC_FLAGS_NOOPT += -mp
    CFLAGS         += -mp
    LDFLAGS        += -mp
  endif

  ifeq ($(DEBUG),TRUE)
    FC_FLAGS       += -g -trapuv -Wuninitialized
  else
    # Check for override of default Fortran compiler optimizations
    ifeq ($(F_OPTIMIZATION_OVERRIDE),$(null))
      FORTRAN_OPTIMIZATION := -O
    endif
    FC_FLAGS += $(FORTRAN_OPTIMIZATION)
  endif

  FFLAGS       := $(cpp_path) $(mod_path) $(CPPDEF) $(FC_FLAGS)
  FFLAGS_NOOPT := $(cpp_path) $(mod_path) $(CPPDEF) $(FC_FLAGS_NOOPT)
  FC_AUTO_R8   := -r8

# These RRTMG files take an extraordinarily long time to compile with optimization.
# Until mods are made to read the data from files, just remove optimization from
# their compilation.
rrtmg_lw_k_g.o: rrtmg_lw_k_g.f90
	$(FC) -c $(FREEFLAGS) $(FFLAGS_NOOPT) $<
rrtmg_sw_k_g.o: rrtmg_sw_k_g.f90
	$(FC) -c $(FREEFLAGS) $(FFLAGS_NOOPT) $<

endif

# g95

ifeq ($(FC_TYPE),g95)

  CPPDEF     += -DG95 -DNO_R16 -DDISABLE_TIMERS -DNO_CRAY_POINTERS
  FC_FLAGS   := -i4 -fno-second-underscore -fstatic  
  FREEFLAGS  := 
  FIXEDFLAGS :=
  LDFLAGS    :=

  ifeq ($(DEBUG),TRUE)
    FC_FLAGS += -g -fbounds-check
  else
    # Check for override of default Fortran compiler optimizations
    ifeq ($(F_OPTIMIZATION_OVERRIDE),$(null))
      FORTRAN_OPTIMIZATION := 
    endif
    FC_FLAGS += $(FORTRAN_OPTIMIZATION)
  endif

  FFLAGS := $(cpp_path) $(mod_path) $(CPPDEF) $(FC_FLAGS)
  FC_AUTO_R8 := -r8

endif

# Flags common to all compilers
ifneq ($(strip $(LAPACK_LIBDIR)),)
  LDFLAGS += -L$(LAPACK_LIBDIR) -llapack -lblas
endif

ifeq ($(SPMD),TRUE)
  FFLAGS += 
  ifneq ($(strip $(LIB_MPI)),)
    LDFLAGS += -L$(LIB_MPI) -l$(MPI_LIB_NAME)
  endif
else
  FFLAGS  += -DHIDE_MPI -D_MPISERIAL -DNO_MPI2
endif

endif


#------------------------------------------------------------------------
# Darwin XLF compiler (serial only, no MPI multi-tasking or OpenMP threading)
#------------------------------------------------------------------------

ifeq ($(UNAMES),Darwin)

CPPDEF     += -DAIX -DDarwin

cpre = $(null)-WF,-D$(null)
FPPFLAGS   := $(patsubst -D%,$(cpre)%,$(CPPDEF))

FC := xlf90_r

CC         := xlc
CFLAGS     := $(cpp_path) $(CPPDEF) -O2
mod_path   := -I$(MOD_NETCDF)
FFLAGS     := $(cpp_path) $(mod_path) $(FPPFLAGS) -qspillsize=2500 
FREEFLAGS  := -qsuffix=f=f90:cpp=F90
FIXEDFLAGS := -qfixed=132
LDFLAGS    := -lSystemStubs -lSystemStubs_profile

ifeq ($(DEBUG),TRUE)
  # Only turn float-trapping on for debug mode as it's a performance hit.
  FFLAGS += -qinitauto=FF911299 -qflttrap=ov:zero:inv:en -C -qfullpath -qhalt=e
else
  # Check for override of default Fortran compiler optimizations
  ifeq ($(F_OPTIMIZATION_OVERRIDE),$(null))
    FORTRAN_OPTIMIZATION := -O3 -qstrict
  endif
  FFLAGS += $(FORTRAN_OPTIMIZATION)
endif

ifeq ($(SMP),TRUE)
  # SMP not implemented
  FFLAGS  +=
  CFLAGS  +=
  LDFLAGS +=
endif

ifeq ($(SPMD),TRUE)
  # SPMD not implemented
  LDFLAGS +=
else
  FFLAGS  += -WF,-DHIDE_MPI,-D_MPISERIAL,-DNO_MPI2
endif

endif

#------------------------------------------------------------------------
# BGL
#------------------------------------------------------------------------

ifeq ($(UNAMES),BGL)

CPPDEF     += -DAIX -DBGL
BGLPATH=/bgl/BlueLight/ppcfloor/bglsys
cpre = $(null)-WF,-D$(null)
FPPFLAGS   := $(patsubst -D%,$(cpre)%,$(CPPDEF))

FC         := mpxlf90
CC         := mpxlc
CFLAGS     := $(cpp_path) $(CPPDEF) -O2 \
              -I$(BGLPATH)/include
mod_path   := -I$(MOD_NETCDF)
FFLAGS     := -I$(BGLPATH)/include \
               $(cpp_path) $(mod_path) $(FPPFLAGS) -qarch=440 \
		-qspillsize=2500 -g -qfullpath 
FREEFLAGS  := -qsuffix=f=f90:cpp=F90
FIXEDFLAGS := -qfixed=132
LDFLAGS    := -L$(BGLPATH)/lib -lmpich.rts -lmsglayer.rts \
              -lrts.rts -ldevices.rts

ifeq ($(DEBUG),TRUE)
  FFLAGS += -qinitauto=FF911299 -qflttrap=ov:zero:inv:en
else
  # Check for override of default Fortran compiler optimizations
  ifeq ($(F_OPTIMIZATION_OVERRIDE),$(null))
    # Inline when not debugging
    FORTRAN_OPTIMIZATION := -O3 -qstrict -Q
  endif
  FFLAGS += $(FORTRAN_OPTIMIZATION)
endif

ifneq ($(strip $(LAPACK_LIBDIR)),)
  LDFLAGS += -L$(LAPACK_LIBDIR) -llapack -lblas
endif

endif

#------------------------------------------------------------------------
# BGP
#------------------------------------------------------------------------

ifeq ($(UNAMES),BGP)

CPPDEF     += -DAIX -DBGP
ifeq ($(SMP),TRUE)
  # THREADED_OMP is used by the timing library
  CPPDEF   += -DTHREADED_OMP
endif

cpp_path += -I/bgsys/drivers/ppcfloor/arch/include

cpre = $(null)-WF,-D$(null)
FPPFLAGS     := $(patsubst -D%,$(cpre)%,$(CPPDEF))

CC           := /bgsys/drivers/ppcfloor/comm/bin/mpixlc_r
CFLAGS       := $(cpp_path) $(CPPDEF) -O2

FC           := /bgsys/drivers/ppcfloor/comm/bin/mpixlf90_r
mod_path     := -I$(MOD_NETCDF)
FFLAGS       := $(cpp_path) $(mod_path) $(FPPFLAGS) \
		-qspillsize=2500 -g -qfullpath 
FFLAGS_NOOPT := $(FFLAGS)
FREEFLAGS    := -qsuffix=f=f90:cpp=F90
FIXEDFLAGS   := -qfixed=132
LDFLAGS      := $(FFLAGS) -Wl,--relax

ifeq ($(SMP),TRUE)
  FFLAGS_NOOPT += -qsmp=omp:noopt

  # -qsmp implicitly turns on -O2.  Explicitly disable this for debugging.
  ifeq ($(DEBUG),TRUE)
    FFLAGS   += -qsmp=omp:noopt
    CFLAGS   += -qsmp=omp:noopt
    LDFLAGS  += -qsmp=omp:noopt
  else
    FFLAGS   += -qsmp=omp
    CFLAGS   += -qsmp=omp
    LDFLAGS  += -qsmp=omp
  endif
endif

ifeq ($(DEBUG),TRUE)
  FFLAGS       += -O0 -qinitauto=7FF7FFFF -qflttrap=ov:zero:inv:en
  FFLAGS_NOOPT += -O0 -qinitauto=7FF7FFFF -qflttrap=ov:zero:inv:en
else
  # Check for override of default Fortran compiler optimizations
  ifeq ($(F_OPTIMIZATION_OVERRIDE),$(null))
    # Inline when not debugging
    FORTRAN_OPTIMIZATION := -qarch=450 -O3 -Q -qstrict
  endif
  FFLAGS += $(FORTRAN_OPTIMIZATION)
endif

ifneq ($(strip $(LAPACK_LIBDIR)),)
  LDFLAGS += -L$(LAPACK_LIBDIR) -llapack -lblas
endif

# Compile these RRTMG files without optim
# Until mods are made to read the data from files, just remove optimization from
# their compilation.
rrtmg_lw_k_g.o: rrtmg_lw_k_g.f90
	$(FC) -c $(FREEFLAGS) $(FFLAGS_NOOPT) $<
rrtmg_sw_k_g.o: rrtmg_sw_k_g.f90
	$(FC) -c $(FREEFLAGS) $(FFLAGS_NOOPT) $<

endif

#------------------------------------------------------------------------

# Default linker is the Fortran compiler
ifeq ($(strip $(LINKER)),)
  LINKER := $(FC)
endif

# For compiling and linking with external ESMF.
# If linking to external ESMF library then include esmf.mk to provide the macros:
# ESMF_F90COMPILEPATHS
# ESMF_F90LINKPATHS
# ESMF_F90LINKRPATHS
# ESMF_F90ESMFLINKLIBS
ifneq ($(strip $(ESMF_LIBDIR)),)
  include $(ESMF_LIBDIR)/esmf.mk
  FFLAGS  += $(ESMF_F90COMPILEPATHS)
  LDFLAGS += $(ESMF_F90LINKPATHS) $(ESMF_F90LINKRPATHS) $(ESMF_F90ESMFLINKLIBS)
  #override default linker with ESMF recommendation unless user has set linker
  ifeq ($(strip $(USER_LINKER)),)
    LINKER =  $(ESMF_F90LINKER)
  endif
endif

# Append user defined compiler and load flags to Makefile defaults
CFLAGS   += $(USER_CFLAGS)
FFLAGS   += $(USER_FFLAGS)
LDFLAGS  += $(USER_LDFLAGS)

# export variables needed by sub-Make
export FC
export FC_FLAGS
export FC_AUTO_R8
export FREEFLAGS
export FIXEDFLAGS

include $(CURDIR)/Depends
